﻿using JX.Core.Entity;
using JX.Infrastructure.Common;
using Microsoft.EntityFrameworkCore;
using System;

namespace JX.EF
{
	/// <summary>
	/// 创建DbContext的工厂类。
	/// 使用方法：在展示层的Startup.cs文件的ConfigureServices方法中，添加services.AddScoped《IDbContextFactory, DbContextFactory》();
	/// </summary>
	public class DbContextFactory : IDbContextFactory
	{
		private DatabaseConfig databaseConfig = null;
		private string[] ReadConn = null;

		/// <summary>
		/// 从appsettings.json文件中得到数据库配置
		/// </summary>
		public DbContextFactory()
		{
			databaseConfig = ConfigHelper.GetAppSettingSection<DatabaseConfig>();
			ReadConn = databaseConfig.ReadDB.Split(",");
		}

		/// <summary>
		/// 根据枚举，分别创建DbContext
		/// </summary>
		/// <param name="writeAndRead"></param>
		/// <returns></returns>
		public ApplicationDbContext CreateDbContext(WriteAndReadEnum writeAndRead)
		{
			string sqlConn = string.Empty;
			switch (writeAndRead)
			{
				case WriteAndReadEnum.Write:
					sqlConn = databaseConfig.WriteDB;
					break;
				case WriteAndReadEnum.Read:
					sqlConn = GetReadConn();
					break;
				default:
					break;
			}
			var contextOptions = new DbContextOptionsBuilder<ApplicationDbContext>()
				.UseSqlServer(sqlConn, providerOptions => providerOptions.CommandTimeout(90))
				.Options;
			
			return new ApplicationDbContext(contextOptions);
		}

		private string GetReadConn()
		{
			string conn = string.Empty;
			switch ((QueryDBStrategyEnum)databaseConfig.QueryDBStrategy)
			{
				case QueryDBStrategyEnum.Polling://轮询策略
					var polling = new PollingHelper<string>(ReadConn);
					conn = polling.GetNextItem();
					break;
				default://随机策略
					int index = new Random().Next(0, ReadConn.Length - 1);
					conn = ReadConn[index];
					break;
			}
			
			return conn;
		}
	}
}
